﻿using System;
using Microsoft.Practices.EnterpriseLibrary.Logging;

namespace SpLocalizer.Common.Extensions
{
    public static class EventExtensions
    {
        public static void RaiseEvent<T>(this object sender, EventHandler<T> eventToRaise, T eventArgs)
            where T : EventArgs
        {
            EventHandler<T> eventCopy = eventToRaise;

            if (eventCopy != null)
                eventCopy(sender, eventArgs);
        }

        public static void RaiseEvent<T>(this object sender, EventHandler<T> eventToRaise, Func<T> eventArgsCreator)
            where T : EventArgs
        {
            EventHandler<T> eventCopy = eventToRaise;

            if (eventCopy != null)
                eventCopy(sender, eventArgsCreator());
        }

        public static void BeginRaiseEvent<T>(this object sender, EventHandler<T> eventToRaise, T eventArgs)
            where T : EventArgs
        {
            EventHandler<T> eventCopy = eventToRaise;

            if (eventCopy != null)
            {
                foreach (EventHandler<T> handler in eventCopy.GetInvocationList())
                {
                    EventHandler<T> handlerTemp = handler;
                    handler.BeginInvoke(sender, eventArgs, ar =>
                                                               {
                                                                   try
                                                                   {
                                                                       handlerTemp.EndInvoke(ar);
                                                                   }
                                                                   catch (Exception ex)
                                                                   {
                                                                       ServiceContainer.Resolve<LogWriter>().Write(ex.Message, Constants.ExceptionLogCategory);                                                                       
                                                                   }
                                                               }, null);
                }
            }
        }

        public static void BeginRaiseEvent<T>(this object sender, EventHandler<T> eventToRaise, Func<T> eventArgsCreator)
            where T : EventArgs
        {
            EventHandler<T> eventCopy = eventToRaise;

            if (eventCopy != null)
            {
                foreach (EventHandler<T> handler in eventCopy.GetInvocationList())
                {
                    EventHandler<T> handlerTemp = handler;
                    handler.BeginInvoke(sender, eventArgsCreator(), ar =>
                                                                        {
                                                                            try
                                                                            {
                                                                                handlerTemp.EndInvoke(ar);
                                                                            }
                                                                            catch (Exception ex)
                                                                            {
                                                                                ServiceContainer.Resolve<LogWriter>().Write(ex.Message, Constants.ExceptionLogCategory); 
                                                                            }
                                                                        }, null);
                }
            }
        }
    }
}